//
// Created by tcj on 2022/7/16.
//

#ifndef WEB_TEST_HTTPREQUEST_H
#define WEB_TEST_HTTPREQUEST_H
// 解析http的请求信息
// http的请求包括：请求行，请求头部，空行，请求数据四个部分完成的

#include "string"
#include "iostream"
#include "buffer.h"
#include "unordered_map"
#include "unordered_set"
#include "regex"
#include "assert.h"

namespace tcj{
    class HTTPrequest {
    public:
        enum PARSE_STATE{
            REQUEST_LINE,       // http请求数据的开始
            HEADRS,             // http请求数据，解完请求行
            BODY,               // http请求数据，解析完请求头，并且缓冲区还有可读数据
            FINISH,             // 解析完请求数据
        };

        enum HTTP_CODE{
            NO_REQUEST=0,
            GET_REQUEST,
            BAD_REQUEST,
            NO_RESOURSE,
            FORBIDDENT_REQUEST,
            FILE_REQUEST,
            INTERNAL_ERROR,
            CLOSED_CONNECTION,
        };
        HTTPrequest();
        ~HTTPrequest() = default;

        void init();                // 初始化变量
        bool parse(Buffer& buffer); // 解析http请求

        // 获取http信息
        std::string path() const;
        std::string& path();
        std::string method() const;
        std::string version() const;
        std::string getPost(const std::string& key) const;
        std::string getPost(const char* key) const;

        bool isKeepAlive() const;    // 获取的http链接是否keepalive

    private:
        bool parseRequestLine_(const std::string& line);    // 解析请求行
        void parseRequestHeader_(const std::string& line);  // 解析请求头
        void parseDataBody_(const std::string& line);       // 解析数据头

        void parsePath_();  // 解析行的时候，会解析出来路径信息，对路径信息做一个处理
        void parsePost_();  // 处理数据体的时候，如果格式是post，还需要进行解析post报文

        static int convertHex(char ch); // 转换hex格式的函数

        // 实现自动机的state变量
        PARSE_STATE state_;
        // http的方式，路径，版本，数据体
        std::string method_,path_,version_,body_;

        // 分别保存请求头和post解析出来的信息
        std::unordered_map<std::string,std::string> header_;
        std::unordered_map<std::string,std::string> post_;

        // 默认的网页
        static const std::unordered_set<std::string> DEFAULT_HTML_;


    };
}



#endif //WEB_TEST_HTTPREQUEST_H
